#include "stdafx.h"

Pad::Pad()
{

}

void Pad::Render()
{
    if (strokes.size() == 0)
        return;

    if (strokes.size() == 1)
    {
        renderer->RenderQuad(strokes[0].position.x, strokes[0].position.y, strokes[0].brush * 2, strokes[0].brush * 2, BLACK);
        return;
    }

    glColor3fv(BLACK);        
    glLineWidth((float)strokes[0].brush * 2);
	glBegin(GL_LINE_STRIP);

    for (unsigned int i = 1; i < strokes.size(); i++)
    {     
        if (strokes[i - 1].breaker)
        {
            glEnd();
            glColor3fv(BLACK);    
            glLineWidth((float)strokes[i].brush * 2);
	        glBegin(GL_LINE_STRIP);
        }
        else
            renderer->PushLine(strokes[i].position.x, strokes[i].position.y);     
    }

    glEnd();
}

void Pad::InsertStroke(POINT pos, unsigned int brush, bool breaker)
{
    // Check against over lapping
    for (unsigned int i = 0; i < strokes.size(); i++)
    {
        if (abs(strokes[i].position.x - pos.x) < 3.0f && abs(strokes[i].position.y - pos.y) < 3.0f)
            return;
    }

    // Add it to our list of strokes
    Stroke dummy;
    dummy.brush = brush;
    dummy.position = pos;
	dummy.breaker = breaker;
    strokes.push_back(dummy);
}

void Pad::RemoveStroke(POINT pos)
{
    for (unsigned int i = 0; i < strokes.size(); i++)
    {
        if (dist((float)pos.x, (float)pos.y, (float)strokes[i].position.x, (float)strokes[i].position.y) < 10.0f)
        {
			strokes[i-1].breaker = true;
            strokes.erase(strokes.begin() + i);
			return;
        }
    }
}

void Pad::Save()
{
    char writeDir[256];
	sprintf_s(writeDir, "sketch.pad");

	unsigned int size = 0;
    char *buffer = new char[strokes.size() * 24];

	// Write down stroke data
    for (unsigned int i = 0; i < strokes.size(); i++)
    {
        *(unsigned int *)(buffer + size) = strokes[i].brush; size += sizeof(unsigned int);
        *(LONG *)(buffer + size) = strokes[i].position.x; size += sizeof(LONG);
        *(LONG *)(buffer + size) = strokes[i].position.y; size += sizeof(LONG);
		*(bool *)(buffer + size) = strokes[i].breaker; size += sizeof(bool);
    }

	FILE * pFile = fopen (writeDir, "wb");

	if (pFile)
	{
		fwrite(buffer, 1, size, pFile);
	}

	fclose (pFile);

	delete buffer;

    printf("sketch.pad saved.\n");
}

void Pad::Load()
{
    char loadDir[256];
	sprintf_s(loadDir, "sketch.pad");

	FILE *pFile;
	long lSize;
	char *buffer;
	size_t result;

	pFile = fopen(loadDir, "rb");
	if (pFile==NULL) 
	{
		MessageBox ( NULL, TEXT("There's nothing to load!"), TEXT("sketch.pad"), MB_OK );
		return;
	}

	// obtain file size:
	fseek (pFile, 0, SEEK_END);
	lSize = ftell (pFile);
	rewind (pFile);

	// allocate memory to contain the whole file:
	buffer = (char*) malloc (sizeof(char)*lSize);
	if (buffer == NULL) 
	{
		fputs("Memory error", stderr);
		return;
	}

	// copy the file into the buffer:
	result = fread(buffer, 1, lSize, pFile);
	if (result != lSize) 
	{
		fputs("Reading error", stderr); 
		return;
	}

	fclose (pFile);

    // Clear sketch pad and load in new data
    strokes.clear(); 

	unsigned int sizeUnpacked = 0;

    while ((long)sizeUnpacked < lSize)
	{
		unsigned int brush = *(unsigned int *)(buffer + sizeUnpacked); sizeUnpacked += sizeof(unsigned int);
        
        POINT pos;
        pos.x = *(LONG *)(buffer + sizeUnpacked); sizeUnpacked += sizeof(LONG);
        pos.y = *(LONG *)(buffer + sizeUnpacked); sizeUnpacked += sizeof(LONG);

		bool breaker = *(bool *)(buffer + sizeUnpacked); sizeUnpacked += sizeof(bool);

        InsertStroke(pos, brush, breaker);
    }

    printf("sketch.pad loaded\n");
}
